package com.sr.aspect;

import com.alibaba.fastjson.JSON;
import com.sr.annotation.Log;
import com.sr.constant.Constant;
import com.sr.dao.LogDao;
import com.sr.pojo.SysLog;
import com.sr.util.JwtTokenUtil;
import com.sr.util.ToolUtil;
import io.jsonwebtoken.Claims;
import lombok.RequiredArgsConstructor;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.stereotype.Component;

import javax.servlet.http.HttpServletRequest;
import java.lang.reflect.Method;
import java.util.Date;

/**
 * @author xiaochi
 * @date 2022/4/30 15:57
 * @desc LogAspect
 */
@Component
@RequiredArgsConstructor(onConstructor = @__)
public class LogAspect extends AbstractAspect<Object> {

    private final LogDao logDao;

    /**
     * 抽象方法（需要具体实现）
     * @param joinPoint
     * @param method
     * @param request
     * @return
     */
    @Override
    protected Object execute(ProceedingJoinPoint joinPoint, Method method, HttpServletRequest request) {
        return this.save(joinPoint,method,request);
    }

    /**
     * 日志入库
     * @param joinPoint
     * @param method
     * @param request
     * @return
     */
    private Object save(ProceedingJoinPoint joinPoint, Method method, HttpServletRequest request){
        MethodSignature signature = (MethodSignature) joinPoint.getSignature();
        String className = joinPoint.getTarget().getClass().getName();
        String methodName = joinPoint.getSignature().getName();
        SysLog sysLog = new SysLog();
        sysLog.setId(ToolUtil.nextId());
        sysLog.setMethod(className+"."+methodName);
        Object[] args = joinPoint.getArgs();
        try {
            sysLog.setParams(args.length != 0 ? JSON.toJSONString(args) : "");
        }catch (Exception ignored){}
        String token = request.getHeader(Constant.User.ACCESS_TOKEN);
        Claims claims = JwtTokenUtil.parseToken(token);
        if (claims != null){
            sysLog.setUserId(claims.getSubject());
            sysLog.setUsername((String) claims.get(Constant.User.JWT_USERNAME));
        }
        Log logs = method.getAnnotation(Log.class);
        sysLog.setOperation(logs.module()+"-"+logs.action());
        sysLog.setTime((long)request.getAttribute("time"));
        sysLog.setIp(request.getRemoteAddr());
        sysLog.setCreateTime(new Date());
        //log.info("【操作日志数据】，{}",sysLog.toString());
        return logDao.insert(sysLog);
    }
}
